////////////////////////////////////////////////////////////////////
// Génération d'un patch IPS modifié pour Chrono Cross
////////////////////////////////////////////////////////////////////

////////////////////////////////////////////////////////////////////
// Nemesis pour Terminus Traduction (tt_nemesis@yahoo.fr)
// Date de création :		24/07/04
// Dernière modification :	24/07/04
////////////////////////////////////////////////////////////////////

// Entete
#include "Ips.h"

/*------------------------------------------------------------------
  Création d'un fichier IPS (sans RLE avec code 32bits,8bits)
--------------------------------------------------------------------
 <- fich_in = fichier avant
 <- fich_out = fichier après
 <- fich_ips = fichier IPS résultant
------------------------------------------------------------------*/
void Ips_Creation (char *fich_in, char *fich_out, char *fich_ips)
{
	// Fichiers
	FILE *in_f, *out_f, *ips_f;
	// Octets lus
	// (on buffeurise même pas, pour pas gérer les raccords)
	char ic,oc;
	// Paramètre IPS
	unsigned int p; // (offset sur 32 bits)
	unsigned char l; // (longueur sur 8 bits)
	unsigned char buf[256]; // (buffer de stockage)

	Main_Message_S("\nCreation de l'Ips pour %s...",fich_in,OK);

	// Ouverture des fichiers à comparer
	in_f=fopen(fich_in,"rb");
	out_f=fopen(fich_out,"rb");

	if (in_f==NULL || out_f==NULL) {
		Main_Message_S("Erreur d'ouverture des fichiers.\n","",ER);
		return;
	}

	// Ouverture du fichier de sortie
	ips_f=fopen(fich_ips,"wb");

	if (ips_f==NULL) {
		Main_Message_S("Erreur de creation de l'IPS.\n","",ER);
		return;
	}

	// Initialisation des paramètres
	l=0;
	p=0;
	// Parcours du fichier
	ic=fgetc(in_f);
	oc=fgetc(out_f);
	while (feof(out_f)==0) {
		// Fin du fichier d'entrée
		if (feof(in_f)!=0)
			ic=oc+1; // Pour être sûr qu'ils sont différents
		// Cas d'écriture
		if (l==255 || (ic==oc && l!=0)) {
			fwrite(&p,sizeof(p),1,ips_f);
			fwrite(&l,sizeof(l),1,ips_f);
			fwrite(buf,sizeof(char),l,ips_f);
			p+=l;
			l=0;
		}
		// Comparaison d'octets
		if (ic!=oc) {
			buf[l]=oc;
			l++;
		} else
			p++;
		// Caractères suivants
		ic=fgetc(in_f);
		oc=fgetc(out_f);
	}
	// Dernier élément éventuel
	if (l>0) {
		fwrite(&p,sizeof(p),1,ips_f);
		fwrite(&l,sizeof(l),1,ips_f);
		fwrite(buf,sizeof(char),l,ips_f);
	}

	// Fermeture
	fclose(in_f);
	fclose(out_f);
	fclose(ips_f);

	Main_OK();
}

/*------------------------------------------------------------------
  Application d'un fichier IPS défini ci-dessus
--------------------------------------------------------------------
 <- fich_in = fichier sur lequel appliquer
 <- fich_ips = fichier IPS à appliquer
------------------------------------------------------------------*/
void Ips_Application (char *fich_in, char *fich_ips)
{
	// Fichiers
	FILE *in_f, *ips_f;
	// Paramètre IPS
	unsigned int p; // (offset sur 32 bits)
	unsigned char l; // (longueur sur 8 bits)
	unsigned char buf[256]; // (buffer de stockage)

	Main_Message_S("\nApplication Ips à %s...",fich_in,OK);

	// Ouverture des fichiers
	in_f=fopen(fich_in,"r+b");
	ips_f=fopen(fich_ips,"rb");

	if (in_f==NULL || ips_f==NULL) {
		Main_Message_S("Erreur d'ouverture des fichiers.\n","",ER);
		return;
	}

	// Lecture des premières infos
	fread(&p,sizeof(p),1,ips_f);
	fread(&l,sizeof(l),1,ips_f);
	// Parcours de l'Ips
	while (feof(ips_f)==0) {
		// Chargement et copie du buffer
		fread(buf,sizeof(char),l,ips_f);
		fseek(in_f,p,SEEK_SET);
		fwrite(buf,sizeof(char),l,in_f);
		// Passage à l'élément suivant
		fread(&p,sizeof(p),1,ips_f);
		fread(&l,sizeof(l),1,ips_f);
	}

	// Fermeture
	fclose(in_f);
	fclose(ips_f);

	Main_OK();
}